package ue

import (
	"crypto/rsa"
	"cybertwin/utils/cryptotools"
	"cybertwin/utils/protocol"
	"cybertwin/utils/timer"
	"fmt"
	"sync"

	"github.com/panjf2000/gnet/v2"
	log "github.com/sirupsen/logrus"
)

type CybertwinClient struct {
	gnet.BuiltinEventEngine
	eng               gnet.Engine
	uePrivateKey      *rsa.PrivateKey // 设备自身的密钥对
	TimerForReconnect *timer.Timer
	R3                int
	Ueid              string
	CanRequest        bool
	Token             []byte
	Ck3               []byte
	Wg                *sync.WaitGroup
	Ip                string
	Port              string
	Req_map           map[uint32]*timer.Timer
}

type connContext struct {
	ck3 []byte
}

func (client *CybertwinClient) OnBoot(eng gnet.Engine) (action gnet.Action) {
	log.Infoln("[CtClient OnBoot]-cybertwin client starting")
	client.eng = eng
	client.uePrivateKey = cryptotools.RSA_LoadPrivateKey("./ca/ue", "ue_sk_1.pem")
	return
}

func (client *CybertwinClient) OnOpen(conn gnet.Conn) (out []byte, action gnet.Action) {
	err := client.handler_ACCESS_CYBERTWIN(conn)
	if err != nil {
		log.Errorln("[ctClient OnOpen]:", err.Error())
		action = gnet.Close
	}
	return
}

func (client *CybertwinClient) OnTraffic(conn gnet.Conn) (action gnet.Action) {
	codec := protocol.CodecUtils.AccessProtocolCodec
	data, typeName, _, err := codec.Decode(conn)
	if err != nil {
		return
	}
	//log.Infoln("[ctClient OnTraffic]-成功解析数据包")
	switch typeName {
	case protocol.TYPE_ACCESS_CYBERTWIN_RESP.GetName():
		err := client.handler_ACCESS_CYBERTWIN_RESP(data, conn)
		if err != nil {
			log.Errorln("[ctClient OnTraffic]-[TYPE_ACCESS_CYBERTWIN_RESP]-", err.Error())
		}
		client.CanRequest = true
		client.Req_map = make(map[uint32]*timer.Timer)
		fmt.Println("-----------------------")
		client.Wg.Done()
	case protocol.TYPE_CYBERTWIN_UE_RESPONSE.GetName():
		_, err := client.handler_CYBERTWIN_UE_RESPONSE(data)
		if err != nil {
			log.Errorln("[ctClient OnTraffic]-[TYPE_CYBERTWIN_UE_RESPONSE]-", err.Error())
		}
	}
	return
}
